/*
 * Copyright 2008-2023 dexian.vip. All rights reserved.
 * Support: http://www.dexian.vip
 * License: http://www.dexian.vip/license
 */

package vip.dexian.common.custom.editor;

import vip.dexian.common.CommonAttributes;
import vip.dexian.common.utils.LocalDateTimeUtils;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.lang3.time.DateUtils;

import java.beans.PropertyEditorSupport;
import java.text.ParseException;
import java.time.LocalDateTime;
import java.util.Date;

/**
 * LocalDateTime 属性编辑器，将日期转换为LocalDateTime类型。将所有符合patterns的日期转换为LocalDateTime。
 * <p>
 * 支持的格式有{@link java.time.LocalDateTime#toString()}：
 * <p>
 * 1.  yyyy -> yyyy-01-01T00:00
 * <p>
 * 2. yyyy-MM -> yyyy-MM-01T00:00
 * <p>
 * 3. yyyyMM -> yyyy-MM-01T00:00
 * <p>
 * 4. yyyy/MM -> yyyy-MM-01T00:00
 * <p>
 * 5. yyyy年MM月->yyyy-MM-01T00:00
 * <p>
 * 6.  yyyy-MM-dd-> yyyy-MM-ddT00:00
 * <p>
 * 7. yyyyMMdd-> yyyy-MM-ddT00:00
 * <p>
 * 8. yyyy/MM/dd-> yyyy-MM-ddT00:00
 * <p>
 * 9. yyyy年MM月dd日-> yyyy-MM-ddT00:00
 * <p>
 * 10. yyyy-MM-dd HH:mm:ss-> yyyy-MM-ddT00:00:00
 * <p>
 * 11. yyyyMMddHHmmss-> yyyy-MM-ddT00:00:00
 * <p>
 * 12. yyyy/MM/dd HH:mm:ss-> yyyy-MM-ddT00:00:00
 * <p>
 * 13. yyyy年MM月dd日 HH:mm:ss-> yyyy-MM-ddT00:00:00
 * <p>
 * 14. HH:mm:ss-> 1970-01-01T00:00，仅当ss大于0时，才会返回 1970-01-01T00:00:00
 * <p>
 * 15. HH:mm -> 1970-01-01T00:00
 * {@link CommonAtt.DatePattern}
 *
 * @author 挺好的 2023年05月30日 8:14
 */
public class LocalDateTimeEditor extends PropertyEditorSupport {

    /**
     * 空值处理成null
     */
    private boolean emptyAsNull;

    /**
     * 默认日期格式
     */
    private String dateFormat = CommonAttributes.DatePattern.DATE_TIME_1;

    /**
     * 创建LocalDateTimeEditor
     *
     * @param emptyAsNull
     *         遇见空字符串（去除左右空格）是否转换为null
     */
    public LocalDateTimeEditor (boolean emptyAsNull) {
        this.emptyAsNull = emptyAsNull;
    }

    /**
     * 创建LocalDateTimeEditor
     *
     * @param emptyAsNull
     *         遇见空字符串（去除左右空格）是否转换为null
     * @param dateFormat
     *         日期格式{@link vip.dexian.common.CommonAttributes.DatePattern#PATTERNS}
     */
    public LocalDateTimeEditor (boolean emptyAsNull, String dateFormat) {
        this.emptyAsNull = emptyAsNull;
        this.dateFormat  = dateFormat;
    }

    /**
     * 转换成{@link vip.dexian.common.CommonAttributes.DatePattern#DATE_TIME_1}格式
     *
     * @return 如果日期为空，返回空字符{@link org.apache.commons.lang3.StringUtils#EMPTY}
     */
    @Override
    public String getAsText () {
        LocalDateTime localDateTime = (LocalDateTime) this.getValue();

        if (localDateTime == null) {
            return StringUtils.EMPTY;
        }

        return LocalDateTimeUtils.format(this.dateFormat, localDateTime);
    }

    /**
     * text == null ，set value null
     * <p>
     * value = value.trim()
     * <p>
     * (emptyAsNull && StringUtils.isEmpty(value)) ，set value null.
     *
     * <p>
     * {@link vip.dexian.common.utils.LocalDateTimeUtils#of(java.util.Date)}
     *
     * @param text
     *         日期
     */
    @Override
    public void setAsText (String text) {
        if (text == null) {
            this.setValue(null);
            return;
        }

        String value = text.trim();

        if (this.emptyAsNull && StringUtils.isEmpty(value)) {
            this.setValue(null);
            return;
        }

        try {
            // 此处是一个通用的日期编辑器，先将接收到的日期转换成Date，然后再转换成LocalDateTime，
            // 如果不转换成Date，那么将需要注册LocalDate、LocalTime、LocalDateTime等关联的编辑器
            // DateUtils#parseDate使用的FastDateParser，线程安全且号称速度最快的日期转换工具类
            Date date = DateUtils.parseDate(value, CommonAttributes.DatePattern.PATTERNS);

            this.setValue(LocalDateTimeUtils.of(date));
        } catch (ParseException e) {
            this.setValue(null);
        }
    }
}
